﻿#include "StdAfx.h"
#include "IdentificationCrossing.h"



CIdentificationCrossing::CIdentificationCrossing(void)
{
}


CIdentificationCrossing::~CIdentificationCrossing(void)
{
}

int CIdentificationCrossing::InitConfig(HINSTANCE m_hInstance)
{
	int iresult = CIdentificationVision::InitConfig(m_hInstance);
	return iresult;
}

int CIdentificationCrossing::InitConfig(const WSysConfigString& filename)
{
	int iresult = CIdentificationVision::InitConfig(filename);
	if(iresult != 0 )
	{
		return iresult;
	}

	/////////////////////装载识别文件////////////////////////////////////////////////
	CString fileidentification;
	readcfg.ReadConfigData(_T("Identification"),_T("TrajectoryModel"),fileidentification);
	fileidentification = CFilyFunction::GetFileFullPath(filename.c_str(),fileidentification);
	CVisionModelLoad::LoadVisionMap(fileidentification,m_identTrajectory);

	readcfg.ReadConfigData(_T("Identification"),_T("RangeModel"),fileidentification);
	fileidentification = CFilyFunction::GetFileFullPath(filename.c_str(),fileidentification);
	CVisionModelLoad::LoadVisionMap(fileidentification,m_identRange);

	CString strdata;
	readcfg.ReadConfigData(_T("Identification"),_T("ClassifierColor"),strdata);
	m_ClassifierClr = _wtoi(strdata.GetBuffer());
	return iresult;
}

// Identification
void CIdentificationCrossing::Identification(void)
{
	//读取区域信息
	std::list< IdentificationData > m_rangdata;
	IdentificationData identification;
	if(m_Range.size() < 1)
	{
		int inum = 0;
		LPVOID pMap = MapViewOfFile(m_hOutputMapping,FILE_MAP_WRITE,0,0,0);
		if (NULL != pMap)
		{
			char * pdata = (char * )pMap;
			char cnumdata[10];
			memset(cnumdata,0,sizeof(cnumdata));
			memcpy(cnumdata,pdata,6);
			inum = atoi(cnumdata);
			pdata +=6;			
			for(int i =0 ;i < inum ; ++i)
			{				
				memcpy(&identification,pdata,sizeof(IdentificationData));
				pdata += sizeof(IdentificationData);
				m_rangdata.push_back(identification);
			}
		}
		UnmapViewOfFile((LPVOID)pMap); 

		CPoint start;
		CPoint end;
		CPoint point;
		int icol = 0;
		bool bfind = false;
		std::list< IdentificationData > ::iterator itrange;
		std::list< IdentificationData > ::iterator itnext;
		while(m_rangdata.size() > 0)
		{
			bfind = false;
			for(itrange = m_rangdata.begin(); itrange != m_rangdata.end() ; )
			{
				identification = *itrange;
				if(icol == 0)
				{
					start = identification.m_data.line.point1;
					end = identification.m_data.line.point2;
					m_Range[icol++] = start;
					m_Range[icol++] = end;
					start = end;
					bfind = true;
				}
				else
				{
					if(start == identification.m_data.line.point1)
					{
						end = identification.m_data.line.point2;
						m_Range[icol++] = end;
						start = end;
						bfind = true;
					}
				}
				itnext = itrange;
				++itrange;
				if(bfind == true)
				{
					m_rangdata.erase(itnext);
				}
			}
			if(bfind == false)
			{
				break;
			}
		}
	}


	//读取轨迹信息
	if(m_rangdata.size() > 0)
	{
		m_rangdata.clear();
	}
	if(m_Trajectory.size() > 0)
	{
		m_Trajectory.clear();
	}
	{
		int inum = 0;
		LPVOID pMap = MapViewOfFile(m_hOutputMapping,FILE_MAP_WRITE,0,0,0);
		if (NULL != pMap)
		{
			char * pdata = (char * )pMap;
			char cnumdata[10];
			memset(cnumdata,0,sizeof(cnumdata));
			memcpy(cnumdata,pdata,6);
			inum = atoi(cnumdata);
			pdata +=6;			
			for(int i =0 ;i < inum ; ++i)
			{				
				memcpy(&identification,pdata,sizeof(IdentificationData));
				pdata += sizeof(IdentificationData);
				m_rangdata.push_back(identification);
			}
		}
		UnmapViewOfFile((LPVOID)pMap); 

		CPoint start;
		CPoint end;
		CPoint point;
		int irow = 0,icol = 0;
		bool bfind = false;
		std::list< IdentificationData > ::iterator itrange;
		std::list< IdentificationData > ::iterator itnext;
		while(m_rangdata.size() > 0)
		{
			bfind = false;
			for(itrange = m_rangdata.begin(); itrange != m_rangdata.end() ; )
			{
				identification = *itrange;
				if(icol == 0)
				{
					start = identification.m_data.line.point1;
					end = identification.m_data.line.point2;
					m_Trajectory[irow][icol++] = start;
					m_Trajectory[irow][icol++] = end;
					start = end;
					bfind = true;
				}
				else
				{
					if(start == identification.m_data.line.point1)
					{
						end = identification.m_data.line.point2;
						m_Trajectory[irow][icol++] = end;
						start = end;
						bfind = true;
					}
				}
				itnext = itrange;
				++itrange;
				if(bfind == true)
				{
					m_rangdata.erase(itnext);
				}
			}
			icol = 0;
			irow++;
		}
	}
	
	//输出识别结果
	m_Result.clear();
	int rangecol = 0;
	int trajectoryrow = 0,trajectorycol = 0;
	int j = 0,a = 0,b =0;
	double rangeall = 0;	
	int number = 0;
	trajectoryrow = m_Trajectory.size();
	for( a = 0; a < trajectoryrow; ++a);
	{
		trajectorycol = m_Trajectory[a].size();
		rangeall = 0;
		for(b = 0; b<trajectorycol ; ++b)
		{
			rangecol = m_Range.size();
			rangeall = 0;
			point3 = m_Trajectory[a][b];
			for(j = 0; j<rangecol-1 ; ++j)
			{					
				point1 = m_Range[j];
				point2 = m_Range[j+1];
				for( a = 0; a < trajectoryrow; ++a);
				{
					trajectorycol = m_Trajectory[a].size();
					rangeall = 0;
					for(b = 0; b<trajectorycol ; ++b)
					{
						rangeall += TriangleMath(point1, point2, point3);
					}
				}
				rangeall += TriangleMath(point1, point2, point3);
			}
			if(rangeall > 330)
			{
				++number;
			}
		}
		IdentificationData identification;
		identification.m_type[0] = '2';
		identification.m_type[1] = '0';
		memset(identification.m_iden,0,sizeof(identification.m_iden));
		sprintf(identification.m_iden,"%s",identype.c_str());
		identification.m_clr = m_ClassifierClr;
		identification.m_data.stop.point.x = point3.x;
		identification.m_data.stop.point.y = point3.y;
		identification.m_data.stop.number = number;
		m_Result.push_back(identification);
	}

	///////////////输出识别结果状态/////////////////////////////////////////
	std::list< IdentificationData >::iterator ship = m_Result.begin();
	{
		LPVOID pMap = MapViewOfFile(m_hOutputMapping,FILE_MAP_WRITE,0,0,0);
		if (NULL != pMap)
		{
			memset(pMap,0,1024);
			char * pdata = (char * )pMap;
			sprintf(pdata,"%06d",m_Result.size());
			pdata +=6;
			for( ; ship !=  m_Result.end(); ++ship)
			{
				IdentificationData square = *ship;
				memcpy( pdata, &square, sizeof(IdentificationData) );
				pdata +=sizeof(IdentificationData);
			}
		}
		UnmapViewOfFile((LPVOID)pMap); 
	}

	///////////////输出识别结果状态/////////////////////////////////////////
	{
		LPVOID pMap = MapViewOfFile(m_hReadyMapping,FILE_MAP_WRITE,0,0,0);
		if (NULL != pMap)
		{
			memset(pMap,0,10);
			memcpy(pMap,"0",1);
		}
		UnmapViewOfFile((LPVOID)pMap); 
	}
}

//// LoadModelDll
//int CIdentificationCrossing::LoadModelDll(const WSysConfigString& fileidentification
//	,IdentificationStruct& identification)
//{
//	WSysConfigString strdata;
//	WSysConfigString data;
//	WSysConfigString inifile;
//	CReadConfig readidentification;
//	identification.m_FileName = fileidentification;
//	//identification.m_loadhandle = AfxLoadLibrary(identification.m_FileName.c_str());//\\Program Files\\CarEngineDlg
//	//if(identification.m_loadhandle==NULL){
//	//	WSysConfigString strerror = L"加载失败:" + identification.m_FileName + L"失败!";
//	//	::MessageBox(::GetDesktopWindow(),strerror.c_str(),L"操作失败",MB_OK);
//	//	return -1;
//	//}
//	inifile = identification.m_FileName.substr(0,identification.m_FileName.length()-3) + _T("ini");
//	identification.m_IniName = inifile;
//	readidentification.SetConfigFileName(inifile);
//	readidentification.ReadConfigData(_T("Identification"),_T("InitConfig"),data);
//	identification.f_initconfig = (IdentificationStruct::InitConfig)::GetProcAddress(identification.m_loadhandle,("InitConfig"));
//	readidentification.ReadConfigData(_T("Identification"),_T("DealwithIdentification"),data);
//	identification.f_dealwithidentification = 
//		(IdentificationStruct::DealwithIdentification)::GetProcAddress(identification.m_loadhandle,("DealwithIdentification"));
//	readidentification.ReadConfigData(_T("Identification"),_T("StartIdentification"),data);
//	identification.f_startidentification = 
//		(IdentificationStruct::StartIdentification)::GetProcAddress(identification.m_loadhandle,("StartIdentification"));
//	readidentification.ReadConfigData(_T("Identification"),_T("StopIdentification"),data);
//	identification.f_stopidentification = 
//		(IdentificationStruct::StopIdentification)::GetProcAddress(identification.m_loadhandle,("StopIdentification"));
//	
//	readidentification.ReadConfigData(_T("Identification"),_T("IdentStatus"),data);
//	identification.m_identstatus = _wtoi(data.c_str());
//
//	readidentification.ReadConfigData(_T("Identification"),_T("OutputMedia"),data);	
//	data = CFilyFunction::GetFileByPath(data);
//	identification.m_hOutputMapping = OpenFileMapping(FILE_MAP_READ|FILE_MAP_WRITE,false,data.c_str());
//	if (NULL == identification.m_hOutputMapping)
//	{
//		return -1;
//	}
//	readidentification.ReadConfigData(_T("Identification"),_T("ReadyStatus"),data);
//	data = CFilyFunction::GetFileByPath(data);
//	identification.m_hReadyMapping = OpenFileMapping(FILE_MAP_READ|FILE_MAP_WRITE,false,data.c_str());
//	if (NULL == identification.m_hReadyMapping)
//	{
//		return -1;
//	}
//	return 0;
//}


// ClearMapSetting
void CIdentificationCrossing::ClearMapSetting(void)
{
	if(m_identTrajectory.m_hReadyMapping != NULL)
	{
		CloseHandle(m_identTrajectory.m_hReadyMapping);
	}
	if(m_identTrajectory.m_hOutputMapping != NULL)
	{
		CloseHandle(m_identTrajectory.m_hOutputMapping);
	}
	FreeLibrary(m_identTrajectory.m_loadhandle);

	if(m_identRange.m_hReadyMapping != NULL)
	{
		CloseHandle(m_identRange.m_hReadyMapping);
	}
	if(m_identRange.m_hOutputMapping != NULL)
	{
		CloseHandle(m_identRange.m_hOutputMapping);
	}
	FreeLibrary(m_identRange.m_loadhandle);


}



// TriangleMath
//a²=b²+c²-2bccosA
//b²=a²+c²-2accosB
//c²=a²+b²-2abcosC
double CIdentificationCrossing::TriangleMath(const CPoint & point1, const CPoint & point2, const CPoint & point3)
{
	long linea = std::powf((point1.x - point2.x),2) + std::powf((point1.y - point2.y),2);
	long lineb = std::powf((point2.x - point3.x),2) + std::powf((point2.y - point3.y),2);
	long linec = std::powf((point1.x - point3.x),2) + std::powf((point1.y - point3.y),2);
	double consta = ( lineb  + linec - linea)/(2*std::sqrtf(lineb)*std::sqrtf(linec));
	double atan = std::acosf(consta)*180 /3.1415;
	return atan;
}


